package yxy.game.pm2.module.arena;

import org.joda.time.DateTime;
import org.redisson.api.RList;
import yxy.apple.util.redisson.RedisException;
import yxy.cherry.battle.module.record.result.BattleResult;
import yxy.cherry.game.base.redis.RedisManager;
import yxy.game.pm2.bean.db.newDao.ArenaRecordDAO;
import yxy.game.pm2.bean.db.po.ArenaRecordPo;
import yxy.game.pm2.bean.module.PlayerModule;

import java.util.ArrayList;
import java.util.List;

public class ArenaRecord extends PlayerModule {
    // bean===========================================================================
    private DateTime date;// 时间
    private String recordCode;// 录像code

    private String attackerCode;// 进攻方
    private String defenderCode;// 防守方

    private int scoreChangeAttacker;// 进攻方分数变化
    private int scoreChangeDefender;// 防守方分数变化

    private BattleResult battleResult;

    public DateTime getDate() {
        return date;
    }

    public void setDate(DateTime date) {
        this.date = date;
    }

    public String getRecordCode() {
        return recordCode;
    }

    public void setRecordCode(String recordCode) {
        this.recordCode = recordCode;
    }

    public String getAttackerCode() {
        return attackerCode;
    }

    public void setAttackerCode(String attackerCode) {
        this.attackerCode = attackerCode;
    }

    public String getDefenderCode() {
        return defenderCode;
    }

    public void setDefenderCode(String defenderCode) {
        this.defenderCode = defenderCode;
    }

    public int getScoreChangeAttacker() {
        return scoreChangeAttacker;
    }

    public void setScoreChangeAttacker(int scoreChangeAttacker) {
        this.scoreChangeAttacker = scoreChangeAttacker;
    }

    public int getScoreChangeDefender() {
        return scoreChangeDefender;
    }

    public void setScoreChangeDefender(int scoreChangeDefender) {
        this.scoreChangeDefender = scoreChangeDefender;
    }

    public BattleResult getBattleResult() {
        return battleResult;
    }

    public void setBattleResult(BattleResult battleResult) {
        this.battleResult = battleResult;
    }

    // func===========================================================================
    // redis==========================================================================

    static public String key(String playerCode) {
        return String.format("PLAYER:%s:MODULE:ARENARECORD", playerCode);
    }

    static private RList<ArenaRecord> touch(String playerCode) throws RedisException {
        return RedisManager.client(redis()).getList(key(playerCode));
    }

    static public List<ArenaRecord> get(String playerCode) {
        try {
            List<ArenaRecord> list = touch(playerCode).readAll();
            if (list.size() == 0) {
                List<ArenaRecordPo> arenaRecordPoList = ArenaRecordDAO.getList(playerCode);
                if (arenaRecordPoList != null && arenaRecordPoList.size() > 0) {
                    for (int i = 0; i < arenaRecordPoList.size(); i++) {
                        ArenaRecord arenaRecord = new ArenaRecord();
                        arenaRecord.setPlayerCode(arenaRecordPoList.get(i).getPlayerCode());
                        arenaRecord.setAttackerCode(arenaRecordPoList.get(i).getAttackerCode());
                        arenaRecord.setBattleResult(BattleResult.battleResult(arenaRecordPoList.get(i).getBattleResult()));
                        arenaRecord.setDate(new DateTime((arenaRecordPoList.get(i).getDate())));
                        arenaRecord.setDefenderCode(arenaRecordPoList.get(i).getDefenderCode());
                        arenaRecord.setRecordCode(arenaRecordPoList.get(i).getRecordCode());
                        arenaRecord.setScoreChangeAttacker(arenaRecordPoList.get(i).getScoreChangeAttacker());
                        arenaRecord.setScoreChangeAttacker(arenaRecordPoList.get(i).getScoreChangeDefender());

                        list.add(arenaRecord);
                    }
                    //放回缓存
                    touch(playerCode).addAll(list);
                }
            }

            return list;
        } catch (RedisException e) {
            e.printStackTrace();
            return new ArrayList<>();
        }
    }

    static public void add(String playerCode, ArenaRecord record) {
        try {
            RList<ArenaRecord> rlist = touch(playerCode);
            rlist.add(0, record);
            if (rlist.size() > 20) {
                rlist.trim(0, 19);
            }
        } catch (RedisException e) {
            e.printStackTrace();
        }
    }

    //数据归档到数据库
    public static void saveToDB(String playerCode) {
        try {
            RList<ArenaRecord> rList = touch(playerCode);
            if (rList.isExists()) {
                long updateTime = System.currentTimeMillis();
                //存储
                List<ArenaRecordPo> arenaRecordPoList = new ArrayList<>();
                List<ArenaRecord> list = rList.readAll();
                for (int i = 0; i < list.size(); i++) {
                    ArenaRecordPo arenaRecordPo = new ArenaRecordPo();
                    arenaRecordPo.setPlayerCode(playerCode);
                    arenaRecordPo.setAttackerCode(list.get(i).getAttackerCode());
                    arenaRecordPo.setBattleResult(list.get(i).getBattleResult().toString());
                    arenaRecordPo.setDate(list.get(i).getDate().toDate());
                    arenaRecordPo.setDefenderCode(list.get(i).getDefenderCode());
                    arenaRecordPo.setRecordCode(list.get(i).getRecordCode());
                    arenaRecordPo.setScoreChangeAttacker(list.get(i).getScoreChangeAttacker());
                    arenaRecordPo.setScoreChangeDefender(list.get(i).getScoreChangeDefender());
                    arenaRecordPo.setUpdateTime(updateTime);
                    arenaRecordPoList.add(arenaRecordPo);
                    ArenaRecordDAO.replace(arenaRecordPoList);
                }

                // 当且仅当执行过update或者insert操作之后，侧面证明redis数据没问题。此时才能进行delete操作
                ArenaRecordDAO.delete(playerCode, updateTime);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    //从redis移走数据
    public static void removeAllFromRedis(String playerCode) {
        try {
            touchBucket(key(playerCode)).delete();
        } catch (RedisException e) {
            e.printStackTrace();
        }
    }
    // lock==========================================================================

    @Override
    public String lockKey() {
        return String.format("lock:%s", key(getPlayerCode()));
    }
}
